﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace BrickAndBrick
{
    /// <summary>
    /// 自动化操作类，提供通过模拟鼠标移动，自动化完成过关相关方法
    /// </summary>
    class BBAutoOperation
    {
        [StructLayout(LayoutKind.Sequential)]
        struct POINT
        {
            public int X;
            public int Y;

            public POINT(int x, int y)
            {
                this.X = x;
                this.Y = y;
            }
        }

        [StructLayout(LayoutKind.Sequential)]
        struct RECT
        {
            public int Left;
            public int Top;
            public int Right;
            public int Bottom;
        }

        private const uint MOUSEEVENTF_LEFTDOWN = 0x02;
        private const uint MOUSEEVENTF_LEFTUP = 0x04;

        // 导入Windows API函数
        [DllImport("user32.dll", SetLastError = true)]
        static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

        [DllImport("user32.dll")]
        [return: MarshalAs(UnmanagedType.Bool)]
        static extern bool GetWindowRect(IntPtr hWnd, out RECT lpRect);

        [DllImport("user32.dll")]
        [return: MarshalAs(UnmanagedType.Bool)]
        static extern bool SetCursorPos(int X, int Y);

        [DllImport("user32.dll")]
        static extern void mouse_event(uint dwFlags, uint dx, uint dy, uint dwData, UIntPtr dwExtraInfo);

        [DllImport("winmm.dll", EntryPoint = "timeBeginPeriod")]
        public static extern uint MM_BeginPeriod(uint uMilliseconds);
        [DllImport("winmm.dll", EntryPoint = "timeEndPeriod")]
        public static extern uint MM_EndPeriod(uint uMilliseconds);


        public static void MoveBrick(BBStep step)
        {
            // 查找窗口句柄
            IntPtr hWnd = FindWindow(null, "砖了个砖");
            if (hWnd == IntPtr.Zero)
            {
                Console.WriteLine("窗口未找到!");
                return;
            }

            // 获取窗口的区域
            GetWindowRect(hWnd, out RECT rect);
            POINT windowPos = new POINT(rect.Left, rect.Top);
            POINT mapPos = new POINT(windowPos.X + 10, windowPos.Y + 136);
            POINT startPoint = new POINT(mapPos.X + step.movePos % 10 * 43 + 20, mapPos.Y + step.movePos / 10 * 43 + 20);
            MM_BeginPeriod(1);
            switch (step.moveDirection)
            {
                case 0:
                    MoveLeft(startPoint.X, startPoint.Y, step.moveSteps);
                    break;
                case 1:
                    MoveUp(startPoint.X, startPoint.Y, step.moveSteps);
                    break;
                case 2:
                    MoveRight(startPoint.X, startPoint.Y, step.moveSteps);
                    break;
                case 3:
                    MoveDown(startPoint.X, startPoint.Y, step.moveSteps);
                    break;
                default:
                    break;
            }
            MM_EndPeriod(1);
        }

        static void MoveLeft(int x, int y, int steps)
        {
            if (steps == 0)
            {
                SetCursorPos(x, y);
                mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
                Thread.Sleep(100);
                mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
                return;
            }
            int distence = steps * 43;
            int tik = 560 / distence;
            SetCursorPos(x, y);
            Thread.Sleep(50);
            mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
            for (int i = 0; i < distence / 2; i++)
            {
                SetCursorPos(x -= 2, y);
                Thread.Sleep(tik);
            }
            Thread.Sleep(20);
            mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
        }
        static void MoveUp(int x, int y, int steps)
        {
            if (steps == 0)
            {
                SetCursorPos(x, y);
                mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
                Thread.Sleep(100);
                mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
                return;
            }
            int distence = steps * 43;
            int tik = 560 / distence;
            SetCursorPos(x, y);
            Thread.Sleep(50);
            mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
            for (int i = 0; i < distence / 2; i++)
            {
                SetCursorPos(x, y -= 2);
                Thread.Sleep(tik);
            }
            Thread.Sleep(20);
            mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
        }
        static void MoveRight(int x, int y, int steps)
        {
            if (steps == 0)
            {
                SetCursorPos(x, y);
                mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
                Thread.Sleep(100);
                mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
                return;
            }
            int distence = steps * 43;
            int tik = 560 / distence;
            SetCursorPos(x, y);
            Thread.Sleep(50);
            mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
            for (int i = 0; i < distence / 2; i++)
            {
                SetCursorPos(x += 2, y);
                Thread.Sleep(tik);
            }
            Thread.Sleep(20);
            mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
        }
        static void MoveDown(int x, int y, int steps)
        {
            if (steps == 0)
            {
                SetCursorPos(x, y);
                mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
                Thread.Sleep(100);
                mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
                return;
            }
            int distence = steps * 43;
            int tik = 560 / distence;
            SetCursorPos(x, y);
            Thread.Sleep(50);
            mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
            for (int i = 0; i < distence / 2; i++)
            {
                SetCursorPos(x, y += 2);
                Thread.Sleep(tik);
            }
            Thread.Sleep(20);
            mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
        }
    }
}
